/**
 * ES6新增
 *  弱映射WeakMap，相比较Map，其Weak是指JS垃圾回收程序对待“弱映射”中键的方式。
 * 6.5.1 基本API
 * const weakMap = new WeakMap()
 *  键的类型限制：对于弱映射中的键（key）的类型，只能是Object或者继承Object的类型，否则会抛出TypeError。
 *  值没有限制
 * 初始化：
 *  使用嵌套数组初始化
 *  使用get()和has()查询，使用set()添加键值对，使用delete()删除
 * 6.5.2 弱键 意思就是把key设置成null，那这个键值对就回自动被回收
 *  WeakMap 中“weak”表示弱映射的键是“弱弱地拿着”的。意思就是，这些键不属于正式的引用，不会阻止垃圾回收。
 *  6.5.3 不可迭代键
 *  因为 WeakMap 中的键/值对任何时候都可能被销毁，所以没必要提供迭代其键/值对的能力。
 *  6.5.4 使用弱映射
 *      1. 私有变量
 *      2. DOM节点元数据 如果dom节点小时那么内存会相应的被释放
 *  
 */
const key1 = { id: 1 }
// 原始值可以先包装成对象再用作键 
const stringKey1 = new String("key1");
const wm = new WeakMap([
    [stringKey1, 'val1'],
    [key1,'val2']
])
console.log(wm.get(stringKey1))
console.log(wm.get(key1))

// 使用弱键映射创建一个闭包,变成私有变量
const User = (() => {
    const wm = new WeakMap();
    class User { 
        constructor(id) {
            this.idProperty = Symbol('id')
            this.setId(id)
        }
        setPrivate(property, value) {
            const privateMembers = wm.get(this) || {};
            privateMembers[property] = value;
            wm.set(this, privateMembers);
        }
        getPrivate(property) { 
            return wm.get(this)[property]
        }
        setId(id) { 
            this.setPrivate(this.idProperty, id);
        }
        getId(id) { 
            return this.getPrivate(this.idProperty);
        }
    }   
    return User;
})();
 // dom节点元数据
const wmDom = new WeakMap();
const loginButton = document.querySelector('#login');
wmDom.set(loginButton, { disabled: true });
